#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "freertos/timers.h"
#include "stdio.h"

#define TIMER_PERIOD_MS pdMS_TO_TICKS(1000)          // 1000ms (1秒)
#define ONE_SHOT_TIMER_PERIOD_MS pdMS_TO_TICKS(5000) // 5000ms (5秒)

TimerHandle_t xPeriodicTimer, xOneShotTimer;

void vPeriodicTimerCallback(TimerHandle_t xTimer)
{
    // 获取定时器 ID
    int timer_id = (int)pvTimerGetTimerID(xTimer);
    printf("周期性定时器回调函数被调用, Timer ID: %d\n", timer_id);
}

void vOneShotTimerCallback(TimerHandle_t xTimer)
{
    // 获取定时器 ID
    int timer_id = (int)pvTimerGetTimerID(xTimer);
    printf("一次性定时器回调函数被调用, Timer ID: %d\n", timer_id);
}

void vTimerTask(void *pvParameters)
{
    BaseType_t xTimerStarted;

    // 创建周期性定时器
    xPeriodicTimer = xTimerCreate("PeriodicTimer",
                                  TIMER_PERIOD_MS,
                                  pdTRUE,    // 自动重载
                                  (void *)1, // 定时器 ID
                                  vPeriodicTimerCallback);

    if (xPeriodicTimer != NULL)
    {
        // 启动周期性定时器
        xTimerStarted = xTimerStart(xPeriodicTimer, 0);
        if (xTimerStarted == pdPASS)
        {
            printf("周期性定时器已启动\n");
        }
    }

    // 创建一次性定时器
    xOneShotTimer = xTimerCreate("OneShotTimer",
                                 ONE_SHOT_TIMER_PERIOD_MS,
                                 pdFALSE,   // 一次性
                                 (void *)2, // 定时器 ID
                                 vOneShotTimerCallback);

    if (xOneShotTimer != NULL)
    {
        // 启动一次性定时器
        xTimerStarted = xTimerStart(xOneShotTimer, 0);
        if (xTimerStarted == pdPASS)
        {
            printf("一次性定时器已启动\n");
        }
    }

    // 延迟 3 秒
    vTaskDelay(pdMS_TO_TICKS(3000));

    // 改变周期性定时器的周期
    xTimerChangePeriod(xPeriodicTimer, pdMS_TO_TICKS(2000), 0);
    printf("周期性定时器的周期已修改为 2000ms\n");

    // 延迟 2 秒
    vTaskDelay(pdMS_TO_TICKS(2000));

    // 重置一次性定时器
    xTimerReset(xOneShotTimer, 0);
    printf("一次性定时器已重置\n");

    // 延迟 6 秒
    vTaskDelay(pdMS_TO_TICKS(6000));

    // 停止周期性定时器
    xTimerStop(xPeriodicTimer, 0);
    printf("周期性定时器已停止\n");

    // 删除定时器
    xTimerDelete(xPeriodicTimer, 0);
    printf("周期性定时器已删除\n");

    xTimerDelete(xOneShotTimer, 0);
    printf("一次性定时器已删除\n");

    // 任务删除自己
    vTaskDelete(NULL);
}

int app_main(void)
{
    // 创建一个任务用于定时器测试
    xTaskCreate(vTimerTask, "TimerTask", configMINIMAL_STACK_SIZE, NULL, 1, NULL);

    // 如果代码能够到达这里，说明启动调度器失败
    for (;;)
    {
        vTaskDelay(pdMS_TO_TICKS(2000));
    }
    return 0;
}
